﻿/*
* 公司：Leita Tech
* 版权信息：雷塔所有
* 任务：
* 描述：
* 作者：李大平
* 日期：2020/06/04
*
*/

#include "model/LTHttpRequester.h"

#include <QNetworkReply>
#include <QNetworkAccessManager>
#include <QEventLoop>
#include <QNetworkConfiguration>
#include <QNetworkProxy>

LTHttpRequester::LTHttpRequester(QString url_string,
                             Method method/* = Method::Get*/,
                             QByteArray paras/* = QByteArray()*/,
                             QObject *parent/* = nullptr*/) :
    QObject(parent)
  ,url_string_(url_string)
  ,method_(method)
  ,paras_(paras)
{

}

LTHttpRequester::~LTHttpRequester()
{
    if(reply_ != nullptr)
        delete reply_;
    if(request_ != nullptr)
        delete request_;
    if(network_access_manager_ != nullptr)
        delete network_access_manager_;
}

bool LTHttpRequester::request(const QString& content_type)
{
    qDebug() << "request";
    if(getUrlString().isEmpty()){
        qDebug()<<"LTHttpRequester::request: getUrlString().isEmpty";
        return false;
      }
    QUrl url(getUrlString());
    if(!url.isValid()) {
        qDebug()<<"LTHttpRequester::request: url is invalid";
        return false;
      }
    if(network_access_manager_ == nullptr)
    {
        network_access_manager_ = new QNetworkAccessManager();
        QObject::connect(network_access_manager_, &QNetworkAccessManager::finished, this, &LTHttpRequester::finished);
#ifndef LT_WASM
        QObject::connect(network_access_manager_, &QNetworkAccessManager::sslErrors, this, &LTHttpRequester::sslErrors);
        QObject::connect(network_access_manager_, &QNetworkAccessManager::sslErrors, this, &LTHttpRequester::onSslErrors);
#endif
    }
    if(request_ == nullptr)
    {
        request_ = new QNetworkRequest(url);
    }
    else
        request_->setUrl(url);
#ifndef LT_WASM
    QNetworkConfiguration cfg = network_access_manager_->configuration();
    cfg.setConnectTimeout(getTimeOut());
    if(!getUseCache())
     {
         network_access_manager_->clearAccessCache();
         network_access_manager_->clearConnectionCache();
     }
    network_access_manager_->setConfiguration(cfg);
#endif
    if(!getUseProxy())
        network_access_manager_->setProxy(QNetworkProxy(QNetworkProxy::NoProxy));
#ifndef LT_WASM
    if(getConfigureSsl())
    {
        QSslConfiguration ssl_cfg = request_->sslConfiguration();
        ssl_cfg.setPeerVerifyMode(QSslSocket::PeerVerifyMode::VerifyNone);
        ssl_cfg.setProtocol(QSsl::SslProtocol::TlsV1_0);
        request_->setSslConfiguration(ssl_cfg);
    }
#endif
#ifndef LT_WASM
    request_->setRawHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/71.0.3578.98 Safari/537.36");
#endif
    request_->setRawHeader("Content-Type", QString("application/%1;charset=UTF-8").arg(content_type).toUtf8());
    switch(getMethod())
    {
    case Method::Get:
        reply_ = network_access_manager_->get(*request_);
        break;
    case Method::Post:
        reply_ = network_access_manager_->post(*request_, getParas());
        break;
    case Method::Put:
        reply_ = network_access_manager_->put(*request_, getParas());
        break;
    case Method::Head:
        reply_ = network_access_manager_->head(*request_);
        break;
    default: {
          qDebug()<<"LTHttpRequester::request: Method error";
          return false;
        }
    }
    QObject::connect(reply_, &QNetworkReply::downloadProgress, this, &LTHttpRequester::downloadProgress);
    QObject::connect(reply_, &QObject::destroyed, [=]{
        reply_ = nullptr;
    });
    return true;
}

void LTHttpRequester::setUrlString(QString url_string)
{
    url_string_ = url_string;
}
QString LTHttpRequester::getUrlString() const
{
    return url_string_;
}
void LTHttpRequester::setUseProxy(bool val)
{
    use_proxy_ = val;
}
bool LTHttpRequester::getUseProxy() const
{
    return use_proxy_;
}
#ifndef LT_WASM
void LTHttpRequester::setConfigureSsl(bool val)
{
    configure_ssl_ = val;
}
bool LTHttpRequester::getConfigureSsl() const
{
    return configure_ssl_;
}
#endif
void LTHttpRequester::setMethod(Method val)
{
    method_ = val;
}
LTHttpRequester::Method LTHttpRequester::getMethod() const
{
    return method_;
}
//QNetworkReply *LTHttpRequester::getReply()
//{
//    return reply_;
//}
void LTHttpRequester::abort()
{
    if(reply_!= nullptr)
        reply_->abort();
}
QString LTHttpRequester::errorString() const
{
    if(reply_!= nullptr)
        return reply_->errorString();
    return "";
}
QNetworkRequest *LTHttpRequester::getRequest()
{
    return request_;
}
QNetworkAccessManager *LTHttpRequester::getNetworkAccessManager()
{
    return network_access_manager_;
}
void LTHttpRequester::setParas(QByteArray val)
{
    paras_ = val;
}
QByteArray LTHttpRequester::getParas() const
{
    return paras_;
}
void LTHttpRequester::setUseCache(bool val)
{
    use_cache_ = val;
}
bool LTHttpRequester::getUseCache() const
{
    return use_cache_;
}
void LTHttpRequester::setTimeOut(int val)
{
    time_out_ = val;
}
int LTHttpRequester::getTimeOut() const
{
    return time_out_;
}
#ifndef LT_WASM
void LTHttpRequester::onSslErrors(QNetworkReply *reply, const QList<QSslError> &/*errors*/)
{
    if(reply != nullptr)
        reply->ignoreSslErrors();
}
#endif
